import dagre from '@dagrejs/dagre';
import type { Edge, Node } from '@vue-flow/core';
import { Position, useVueFlow } from '@vue-flow/core';
import { ref } from 'vue';

/**
 * 用于对图进行布局计算的组合式函数
 * 使用 `dagre` 库来计算节点和边的布局（固定从上到下的方向）
 */
export function useLayout() {
  const { findNode } = useVueFlow();

  const graph = ref(new dagre.graphlib.Graph());

  function layout(nodes: Node[], edges: Edge[]) {
    // 创建新的图实例，支持复合图（compound graph）
    const dagreGraph = new dagre.graphlib.Graph({ compound: true });

    graph.value = dagreGraph;

    dagreGraph.setDefaultEdgeLabel(() => ({}));

    // 固定为从上到下的布局方向
    dagreGraph.setGraph({
      rankdir: 'TB',
      // 层级间距：增加垂直间距
      ranksep: 80,
      // 节点间距：控制水平对齐间距
      nodesep: 50,
      // 边间距
      edgesep: 20,
      // 左上对齐：让节点更整齐
      align: 'UL',
    });

    // 第一步：识别所有互斥组
    const mutexGroups = new Map<string, {
      decisionId: string;
      branchIds: string[];
      clusterId: string;
    }>();

    for (const node of nodes) {
      if (node.type === 'mutex-decision') {
        const mutexId = node.data.mutexId || node.id.replace('-decision', '');
        mutexGroups.set(mutexId, {
          decisionId: node.id,
          branchIds: [],
          clusterId: `cluster-${mutexId}`,
        });
      }
    }

    // 第二步：收集每个互斥组的分支节点
    for (const node of nodes) {
      if (node.type === 'mutex-branch') {
        for (const [mutexId, group] of mutexGroups) {
          if (node.id.startsWith(mutexId)) {
            group.branchIds.push(node.id);
            break;
          }
        }
      }
    }

    // 第三步：为每个互斥组创建虚拟的集群节点
    for (const [_mutexId, group] of mutexGroups) {
      // 估算集群的大小
      const branchCount = group.branchIds.length;
      // 每个分支 240px + 30px 间距
      const clusterWidth = branchCount * 270;
      // 足够容纳分支和其子节点
      const clusterHeight = 400;

      dagreGraph.setNode(group.clusterId, {
        width: clusterWidth,
        height: clusterHeight,
      });
    }

    // 第四步：添加所有节点到图中
    for (const node of nodes) {
      const graphNode = findNode(node.id);

      // 为不同类型节点设置合适的尺寸
      const isAddButton = node.type === 'add-button';
      const isMutexDecision = node.type === 'mutex-decision';
      const isMutexBranch = node.type === 'mutex-branch';

      let width = graphNode?.dimensions.width || 150;
      let height = graphNode?.dimensions.height || 50;

      if (isAddButton) {
        width = 50;
        height = 50;
      } else if (isMutexDecision) {
        width = graphNode?.dimensions.width || 180;
        height = graphNode?.dimensions.height || 40;
      } else if (isMutexBranch) {
        width = graphNode?.dimensions.width || 240;
        height = graphNode?.dimensions.height || 100;
      }

      dagreGraph.setNode(node.id, {
        width,
        height,
      });

      // 第五步：将互斥组的节点设置父子关系
      for (const [_mutexId, group] of mutexGroups) {
        if (node.id === group.decisionId || group.branchIds.includes(node.id)) {
          dagreGraph.setParent(node.id, group.clusterId);
        }
      }
    }

    // 第六步：添加边
    for (const edge of edges) {
      dagreGraph.setEdge(edge.source, edge.target);
    }

    // 第七步：执行布局
    dagre.layout(dagreGraph);

    // 第八步：应用布局结果
    const positionedNodes = nodes.map(node => {
      const nodeWithPosition = dagreGraph.node(node.id);

      return {
        ...node,
        targetPosition: Position.Top,
        sourcePosition: Position.Bottom,
        position: {
          x: nodeWithPosition.x - nodeWithPosition.width / 2,
          y: nodeWithPosition.y - nodeWithPosition.height / 2,
        },
      };
    });

    return positionedNodes;
  }

  return { graph, layout };
}
